import requests
from fastapi import APIRouter, HTTPException, status, Request, WebSocket
from tortoise.expressions import Q
from . import scheams, models
from application.utils import wechat_tools, tools
from application.utils.jwt_tool import JwtToken
from datetime import datetime, timedelta
from application import settings
import asyncio
from http import HTTPStatus
import platform

from dashscope import Generation
from dashscope.aigc.generation import AioGeneration

app = APIRouter()


@app.post('/register', response_model=scheams.UserInfoRegResponse)
async def register(request: Request, user_info: scheams.UserInfoRegRequest):
    """用户注册"""
    # 1. 基于code请求微信服务器获取用户的OpenID以及将来调用用户信息的session_key
    result = wechat_tools.get_wechat_info(user_info.code)

    # 0. 根据手机号或微信OpenID判断是否重复注册
    user = await models.User.filter(Q(mobile=user_info.mobile) | Q(openid=result['openid'])).first()
    if user:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='当前手机号/微信号重复注册！')

    # 0. 验证码是否正确
    redis = request.app.state.redis
    sms_code = await redis.get(f'sms_{user_info.mobile}')
    # print(sms_code, user_info.sms_code)

    if not sms_code:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='验证码不存在或填写错误！')

    if sms_code != user_info.sms_code:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='验证码不存在或填写错误！')

    # 在redis中删除已经使用过的验证码
    await redis.delete(f'sms_{user_info.mobile}')

    # 2. 保存数据到用户表
    user = await models.User.create(
        **dict(user_info),
        username=user_info.mobile,
        avatar=user_info.avatarUrl,
        nickname=user_info.nickName,
        sex=user_info.gender,
        openid=result['openid']
    )

    # 注册成功用户，自动登录即可，返回jwt
    token = JwtToken.create_token({
        'id': user.id,
        'username': user.username
    })

    # 3. 返回结构
    return {
        'id': user.id,
        'nickname': user.nickname,
        'avatar': user.avatar,
        'code': 200,
        'err_msg': '用户注册成功',
        'status': 'Success',
        'token': token
    }


@app.post('/login', response_model=scheams.UserInfoRegResponse)
async def login(request: Request, user_info: scheams.UserLoginRequest):
    """用户登录操作"""
    # 0. 判断验证码是否正确
    redis = request.app.state.redis
    sms_code = await redis.get(f'sms_{user_info.mobile}')

    if not sms_code:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='验证码不存在或填写错误！')

    if sms_code != user_info.sms_code:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='验证码不存在或填写错误！')

    # 判断当前用户是否存在
    # 1. 基于code请求微信服务器获取用户的OpenID以及将来调用用户信息的session_key
    result = wechat_tools.get_wechat_info(user_info.code)

    # 0. 根据手机号或微信OpenID判断是否重复注册
    user = await models.User.filter(Q(mobile=user_info.mobile) | Q(openid=result['openid'])).first()
    if not user:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='当前用户不存在！')

    # 判断密码是否正确
    hashing = tools.Hashing()
    ret = hashing.verify(user_info.password, user.password)
    if not ret:
        raise HTTPException(status_code=status.HTTP_422_UNPROCESSABLE_ENTITY, detail='当前账号或密码错误！')
    # 生成token
    token = JwtToken.create_token({
        'id': user.id,
        'username': user.username
    })

    # 记录用户的登陆历史
    await models.UserLoginHistory.create(user=user)

    # 保存Token到redis中
    await redis.setex(f'token_{user.id}', settings.JWT['expire_time'], token)

    # 如果打开限流功能，则初始化用户每天免费使用AI助理的次数到redis中，次日过期
    if settings.AI_ROBOT['limit'] == '1':
        current_time = datetime.now()
        tomorrow = current_time + timedelta(days=1)
        tomorrow_zero = datetime.strptime(f'{tomorrow.year}-{tomorrow.month}-{tomorrow.day}', '%Y-%m-%d')
        delta = tomorrow_zero - current_time
        redis.setex(f'api_{user.id}', delta.seconds, settings.AI_ROBOT['count'])

    # 删除短信验证码，一码多用
    await redis.delete(f'sms_{user_info.mobile}')

    # 返回响应数据
    return {
        'id': user.id,
        'nickname': user.nickname,
        'avatar': user.avatar,
        'code': 200,
        'err_msg': '用户登陆成功',
        'status': 'Success',
        'token': token
    }


async def async_dashscope_sample(message):
    response = await AioGeneration.call("qwen-turbo",
                                        prompt=message)

    return response.output


@app.websocket('/web')
async def main(websocket: WebSocket):
    group_id = "1793261014549008635"
    api_key = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJHcm91cE5hbWUiOiLolKHolKEiLCJVc2VyTmFtZSI6IuiUoeiUoSIsIkFjY291bnQiOiIiLCJTdWJqZWN0SUQiOiIxNzkzMjYxMDE0NTU3Mzk3MjQzIiwiUGhvbmUiOiIxODMzOTI5MjA1OCIsIkdyb3VwSUQiOiIxNzkzMjYxMDE0NTQ5MDA4NjM1IiwiUGFnZU5hbWUiOiIiLCJNYWlsIjoiIiwiQ3JlYXRlVGltZSI6IjIwMjQtMDUtMzAgMTk6MzY6MDEiLCJpc3MiOiJtaW5pbWF4In0.XLH03fJnI4KEsDfH0aPp6YE0XOTwfrdwa6vgEPMD3ySnmLN4nSvv0HGyp56hxgWxoENdhQseziNpo_GTPDmM1tv9x6WDReBg7Fcut-dnLoNTSALU8QnqyCPxlzMu9ElcO0Fqvuc_5l4ePb8o6kV3PB6Jax_I0hMbJfkmJjXWncDU2znWLNHKXDC4Gid2DaaLFFARb1YCizlBl9-p4uarFFmT8FkyUNcwXD--wG2Ggt4Sse7vfv7rB9DHRXotc07ZD39fZnzNfbWIBl5dydeUfzGehv3KqCNvU_LvJZ39bkyROszl3_I7EpNv-B3XN2jRP7kTIJBSPK5HLzMAPAcgnw"

    url = f"https://api.minimax.chat/v1/text/chatcompletion_pro?GroupId={group_id}"
    headers = {"Authorization": f"Bearer {api_key}", "Content-Type": "application/json"}
    await websocket.accept()
    # messages = [
    #     {'role': 'system', 'content': 'You are a helpful assistant'}
    # ]
    #
    # while True:
    #     query = await websocket.receive()
    #     # query = {'role': 'user', 'content': query['text']}
    #     messages.append(query)
    #     # response = await async_dashscope_sample(messages)
    #     response = await async_dashscope_sample(query['text'])
    #     print(response)
    request_body = payload = {
        "model": "abab5.5-chat",
        "tokens_to_generate": 1024,
        "reply_constraints": {"sender_type": "BOT", "sender_name": "MM智能助理"},
        "messages": [],
        "bot_setting": [
            {
                "bot_name": "MM智能助理",
                "content": "MM智能助理是一款由MiniMax自研的，没有调用其他产品的接口的大型语言模型。MiniMax是一家中国科技公司，一直致力于进行大模型相关的研究。",
            }
        ],
    }
    # 添加循环完成多轮交互
    while True:
        # 下面的输入获取是基于python终端环境，请根据您的场景替换成对应的用户输入获取代码
        query = await websocket.receive()
        # 将当次输入内容作为用户的一轮对话添加到messages
        request_body["messages"].append(
            {"sender_type": "USER", "sender_name": "小明", "text": query['text']}
        )
        response = requests.post(url, headers=headers, json=request_body)
        reply = response.json()["reply"]
        #  将当次的ai回复内容加入messages
        request_body["messages"].extend(response.json()["choices"][0]["messages"])
        print(reply)
        await websocket.send_json({"data": reply})

